package com.heima.comment.service.impl;

import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.comment.mapper.CommentMapper;
import com.heima.comment.service.CommentService;
import com.heima.common.aliyun.GreenTextScan;
import com.heima.common.redis.CacheService;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.mongo.comment.dtos.CommentDto;
import com.heima.mongo.comment.dtos.CommentLikeDto;
import com.heima.mongo.comment.dtos.CommentSaveDto;
import com.heima.mongo.comment.pojos.Comment;
import com.heima.mongo.comment.pojos.CommentLikes;
import com.heima.mongo.comment.vos.CommentyVo;
import com.heima.utils.thread.WmThreadLocalUtil;
import lombok.extern.slf4j.Slf4j;

import org.apache.commons.lang3.StringUtils;
import org.checkerframework.checker.units.qual.A;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.FindAndModifyOptions;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.Update;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;

@Service
@Slf4j
@Transactional
public class CommentServiceImpl extends ServiceImpl<CommentMapper, Comment> implements CommentService {

    @Autowired
    private GreenTextScan greenTextScan;
    @Autowired
    private MongoTemplate mongoTemplate;
    @Autowired
    private CacheService cacheService;

    /**
     * 发布评论
     *
     * @param dto
     * @return
     */
    @Override
    public ResponseResult getSave(CommentSaveDto dto) {
        //检验参数
        if (dto == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }
        if (dto.getArticleId() == 0) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }

        if (WmThreadLocalUtil.getUser() == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.NEED_LOGIN, "您未登录");
        }
        if (StringUtils.isBlank(dto.getContent())) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }
        String content = dto.getContent();
        char[] chars = content.toCharArray();
        if (chars.length > 140) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST, "评论字数已达到上限");
        }
        try {
            Map map = greenTextScan.greeTextScan(dto.getContent());
            if (map != null) {
                //审核失败
                if (map.get("suggestion").equals("block")) {
                    return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID, "评论内容设计敏感词汇");
                }
            }
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
        //当前用户登录的id
        Integer UserId = WmThreadLocalUtil.getUser().getApUserId();

        Comment comment = new Comment();
        comment.setEntryId(dto.getArticleId());
        comment.setContent(dto.getContent());
        comment.setUserId(UserId);
        comment.setCreatedTime(new Date());
        mongoTemplate.save(comment);

        return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
    }

    /**
     * 点赞
     *
     * @param dto
     * @return
     */
    @Override
    public ResponseResult like(CommentLikeDto dto) {

        //检验参数
        if (dto == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }
        if (dto.getOperation() == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }
        if (WmThreadLocalUtil.getUser() == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.NEED_LOGIN, "您未登录");
        }
        Criteria criteria = Criteria.where("commentId").is(dto.getCommentId())
                .and("userId").is(WmThreadLocalUtil.getUser().getApUserId());
        Query query = Query.query(criteria);
        //判断数据库中是否有这天数据
        CommentLikes commentLikes = mongoTemplate.findOne(query, CommentLikes.class);
        if (commentLikes == null) {
            commentLikes = new CommentLikes();
            commentLikes.setCommentId(dto.getCommentId());
            commentLikes.setUserId(WmThreadLocalUtil.getUser().getApUserId());
            commentLikes.setCreatedTime(new Date());
            commentLikes.setUpdateTime(new Date());
            if (dto.getOperation() == 0) {
                //如果没有添加状态
                commentLikes.setOperation((short) 0);
                mongoTemplate.save(commentLikes);
            } else {
                commentLikes.setOperation(null);
                mongoTemplate.save(commentLikes);
            }
        } else {
            //如果有修改状态

            if (dto.getOperation() == 0) {
                commentLikes.setOperation((short) 0);
                commentLikes.setUpdateTime(new Date());
                mongoTemplate.save(commentLikes);
            } else {
                commentLikes.setOperation(null);
                commentLikes.setUpdateTime(new Date());
                mongoTemplate.save(commentLikes);
            }
        }
        //记录点赞数量
        Criteria criteria1 = Criteria.where("commentId").is(dto.getCommentId());
        Query query1 = Query.query(criteria);
        Comment comment = mongoTemplate.findOne(query1, Comment.class);
        if (comment == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }
        Update update = new Update();
        if (dto.getOperation() == 0) {
            update.inc("reply", 1);
        } else {
            update.inc("reply", -1);
        }
        FindAndModifyOptions options = new FindAndModifyOptions();
        options.returnNew(true);
        Comment comment1 = mongoTemplate.findAndModify(query1, update, Comment.class);
        Integer likes = comment1.getLikes();
        return ResponseResult.okResult(likes);
    }

    /**
     * 回复评论列表
     *
     * @param dto
     * @return
     */
    @Override
    public ResponseResult load(CommentDto dto) {
        if (dto == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }

        if (dto.getArticleId() == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }
        Long articleId = dto.getArticleId();
        Query query = Query.query(Criteria.where("entryId").is(Long.valueOf(dto.getArticleId()))
                        .and("createdTime").lte(dto.getMinDate()))
                .with(Sort.by(Sort.Order.desc("createdTime")))
                .limit(10);
        List<Comment> comments = mongoTemplate.find(query, Comment.class);
        List<CommentyVo> vos = new ArrayList<>();
        for (Comment comment : comments) {
            CommentyVo vo = new CommentyVo();
            BeanUtils.copyProperties(comment, vo);
            vo.setId(comment.getCommentId().toString());
            vo.setAuthorId(WmThreadLocalUtil.getUser().getApUserId());
            vo.setAuthorName(WmThreadLocalUtil.getUser().getName());
            vo.setType((short) 0);
            vos.add(vo);
        }


        return ResponseResult.okResult(vos);
    }
}
